﻿
using System;
using System.Collections.Generic;
using System.Linq;

namespace Test30.Engine
{
    public class EnergyTimer
    {
        public string Label { get; }

        public EnergyTimer(string label, System.Action elapsedAction, 
            int steps, System.Action stepAction,bool repeat)
        {
            Label = label;
            _elapsedAction = elapsedAction;
            _stepAction = stepAction;
            _energCost = steps * Energy.ActionCost;
            _elapsed = 0;
            _repeat = repeat;
        }

        public EnergyTimer(System.Action elapsedAction, int steps, bool repeat)
            : this(String.Empty, elapsedAction, steps, null, repeat)
        {
        }

        public EnergyTimer(int steps, System.Action stepAction, bool repeat)
            : this(String.Empty, null, steps, stepAction, repeat)
        {
        }

        public bool Elapse(int energy)
        {
            bool done = false;
            int lastStep = _elapsed / Energy.ActionCost;

            _elapsed += energy;
            int thisStep = _elapsed / Energy.ActionCost;

            if(thisStep > lastStep)
            {
                _stepAction?.Invoke();
            }

            if (_elapsed >= _energCost)
            {
                _elapsedAction?.Invoke();
                if (_repeat)
                    _elapsed -= _energCost;
                else
                    done = true;
            }
            return done;
        }

        private readonly System.Action _stepAction;
        private readonly System.Action _elapsedAction;
        private readonly int _energCost;
        private int _elapsed;
        private readonly bool _repeat;
    }

    public class EnergyTimerCollection : List<EnergyTimer>
    {
        internal event EventHandler<EventArgs> TimerRemoved;

        public bool Has(string label)
        {
            return this.Any((timer) => timer.Label == label);
        }

        public void Remove(string label)
        {
            int count = Count;
            this.RemoveAll((timer) => timer.Label == label);

            if (count != Count) OnTimerRemoved();
        }

        public void Gain(int energy)
        {
            int count = Count;
            this.RemoveAll((timer) => timer.Elapse(energy));

            if (count != Count) OnTimerRemoved();
        }
        private void OnTimerRemoved()
        {
            TimerRemoved?.Invoke(this, EventArgs.Empty);
        }
    }
}
